import time
import hmac
import hashlib
import requests
import json
from quant.exchanges.util import parse_params, Socket
from quant.utils import catch_exception


class GateSocket(Socket):
    def _run(self):
        while True:
            if not self._keep_running:
                time.sleep(1)
                continue

            if self.pre_connect_fn:
                self.pre_connect_fn(self._socket)

            try:
                self._socket.run_forever(ping_interval=5, skip_utf8_validation=True)
            except:
                catch_exception()
            time.sleep(5)


def format_symbol(symbol):
    return symbol.replace('/', '_').upper()


def resume_symbol(contract):
    return contract.replace('_', '/').lower()


def is_welcome_data(data):
    return data['event'] == 'subscribe'


def sign(method, path, key, secret, query_string=None, payload_string=None):
    t = time.time()
    m = hashlib.sha512()
    m.update((payload_string or "").encode('utf-8'))
    hashed_payload = m.hexdigest()
    s = '%s\n%s\n%s\n%s\n%s' % (method, path, query_string or "", hashed_payload, t)

    sign = hmac.new(secret.encode('utf-8'), s.encode('utf-8'), hashlib.sha512).hexdigest()
    return {'KEY': key, 'Timestamp': str(t), 'SIGN': sign}


def build_req(method, host, path, key, secret, params=None):
    url = host + path
    headers = {'Accept': 'application/json', 'Content-Type': 'application/json'}
    data = None

    if method == 'POST':
        if params:
            data = json.dumps(params)
        else:
            data = ''
        signed_headers = sign('POST', path, key, secret, None, data)

    elif method == 'GET':
        if params:
            parsed_params = parse_params(params)
            url += '?{}'.format(parsed_params)
        else:
            parsed_params = ''
        signed_headers = sign('GET', path, key, secret, parsed_params)

    elif method == 'DELETE':
        if params:
            parsed_params = parse_params(params)
            url += '?{}'.format(parsed_params)
        else:
            parsed_params = ''
        signed_headers = sign('DELETE', path, key, secret, parsed_params)

    else:
        err = 'request method {} not found'.format(method)
        raise Exception(err)

    headers.update(signed_headers)

    req = requests.Request(method, url, headers, data=data)
    return req


if __name__ == "__main__":
    import keys

    a = keys.get_key('gate_9293')
    key = a['api_key']
    secret = a['secret_key']

    host = "https://api.gateio.ws"
    common_headers = {'Accept': 'application/json', 'Content-Type': 'application/json'}

    # path = '/api/v4/futures/orders'
    # body = {"contract": "BTC_USD", "size": 100, "price": "30", "tif": "gtc"}
    # request_content = json.dumps(body)
    # sign_headers = sign('POST', path, key, secret, "", request_content)
    # sign_headers.update(common_headers)
    # res = requests.post(host + path, headers=sign_headers, data=request_content)

    # path = '/api/v4/spot/my_trades'
    # param = {'currency_pair': 'BTC_USDT'}
    # request_content = parse_params(param)
    # print('param:', request_content)
    # sign_headers = sign('GET', path, key, secret, request_content)
    # res = requests.get(host + path + '?' + request_content, headers=sign_headers)

    # path = '/api/v4/spot/my_trades'
    # params = {'currency_pair': 'BTC_USDT'}
    # path = '/api/v4/spot/accounts'
    # params = {}
    # req = build_req('GET', host, path, key, secret, params)

    path = '/api/v4/spot/orders'
    params = {
        "currency_pair": "ETH_USDT",
        "type": "limit",
        "account": "spot",
        "side": "buy",
        "amount": "1",
        "price": "5.00032",
    }
    req = build_req('POST', host, path, key, secret, params)

    session = requests.Session()
    prep = session.prepare_request(req)
    resp = session.send(prep, timeout=5)


    print(resp.json())














